from peewee import *
import datetime
from passlib.context import CryptContext

# 密码加密上下文
pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")

# 数据库连接
database = SqliteDatabase('qr_app.db')

# 初始化车型
CAR_MODEL_LIST = ["瑶光", "瑶光CDM", "瑞虎9", "虎8L", "艾瑞泽8"]
# 预定义的功能列表
functions = [
    "小鹿灯", "功放", "记录仪", "盲区检测", "倒车侧向制动",
    "紧急车道保持", "索尼音效", "微波雷达", "抬头显示",
    "香氛系统", "方向盘加热", "座椅通风", "前雷达开关",
    "座椅开关", "北斗+hicar", "逸+8155", "尚360"
]


class BaseModel(Model):
    class Meta:
        database = database


class User(BaseModel):
    username = CharField(unique=True, max_length=50)
    email = CharField(unique=True, max_length=100)
    hashed_password = CharField(max_length=255)
    is_active = BooleanField(default=True)
    is_admin = BooleanField(default=False)  # 管理员标识
    generate_limit = IntegerField(default=100)  # 生成接口剩余次数
    created_at = DateTimeField(default=datetime.datetime.now)
    updated_at = DateTimeField(default=datetime.datetime.now)
    
    class Meta:
        table_name = 'users'
    
    def __str__(self):
        return f"User(username={self.username}, email={self.email}, is_admin={self.is_admin}, generate_limit={self.generate_limit})"


class Function(BaseModel):
    name = CharField(unique=True, max_length=100)
    description = CharField(max_length=255, null=True)
    is_active = BooleanField(default=True)
    created_at = DateTimeField(default=datetime.datetime.now)
    
    class Meta:
        table_name = 'functions'
    
    def __str__(self):
        return f"Function(name={self.name})"


class UserFunction(BaseModel):
    user = ForeignKeyField(User, backref='user_functions')
    function = ForeignKeyField(Function, backref='user_functions')
    created_at = DateTimeField(default=datetime.datetime.now)
    
    class Meta:
        table_name = 'user_functions'
        indexes = (
            (('user', 'function'), True),  # 唯一索引
        )
    
    def __str__(self):
        return f"UserFunction(user={self.user.username}, function={self.function.name})"


class CarModel(BaseModel):
    name = CharField(unique=True, max_length=100)
    description = CharField(max_length=255, null=True)
    is_active = BooleanField(default=True)
    created_at = DateTimeField(default=datetime.datetime.now)
    
    class Meta:
        table_name = 'car_models'
    
    def __str__(self):
        return f"CarModel(name={self.name})"


class UserCarModel(BaseModel):
    user = ForeignKeyField(User, backref='user_car_models')
    car_model = ForeignKeyField(CarModel, backref='user_car_models')
    created_at = DateTimeField(default=datetime.datetime.now)
    
    class Meta:
        table_name = 'user_car_models'
        indexes = (
            (('user', 'car_model'), True),
        )
    
    def __str__(self):
        return f"UserCarModel(user={self.user.username}, car_model={self.car_model.name})"


class GenerateHistory(BaseModel):
    user = ForeignKeyField(User, backref='histories')
    created_at = DateTimeField(default=datetime.datetime.now)
    car_model = CharField(max_length=100)
    functions = CharField(max_length=255)  # 逗号分隔
    input_text = TextField()
    output_number = CharField(max_length=255)
    
    class Meta:
        table_name = 'generate_history'
    
    def __str__(self):
        return f"GenerateHistory(user={self.user.username}, car_model={self.car_model}, functions={self.functions}, input={self.input_text}, output={self.output_number})"


# 创建表
def create_tables():
    with database:
        database.create_tables([User, Function, UserFunction, CarModel, UserCarModel, GenerateHistory])


# 密码验证函数
def verify_password(plain_password, hashed_password):
    return pwd_context.verify(plain_password, hashed_password)


# 密码加密函数
def get_password_hash(password):
    return pwd_context.hash(password)


# 初始化默认用户
def init_default_user():
    try:
        # 检查是否已存在默认用户
        if not User.select().where(User.username == 'admin').exists():
            hashed_password = get_password_hash('Shao2580')
            admin_user = User.create(
                username='admin',
                email='admin@example.com',
                hashed_password=hashed_password,
                is_active=True,
                is_admin=True,
                generate_limit=999999  # 管理员无限制
            )
            print("默认管理员用户创建成功: admin/Shao2580")
        else:
            # 如果admin用户已存在，确保它是管理员
            admin_user = User.get(User.username == 'admin')
            if not admin_user.is_admin:
                admin_user.is_admin = True
                admin_user.save()
                print("已将admin用户设置为管理员")
            if admin_user.generate_limit < 99999:
                admin_user.generate_limit = 999999
                admin_user.save()
    except Exception as e:
        print(f"创建默认用户失败: {e}")


# 初始化功能列表
def init_functions():
    try:
        for func_name in functions:
            if not Function.select().where(Function.name == func_name).exists():
                Function.create(name=func_name)
        
        print(f"功能列表初始化完成，共{len(functions)}个功能")
    except Exception as e:
        print(f"初始化功能列表失败: {e}")


# 初始化用户权限
def init_user_permissions():
    try:
        # 获取所有功能
        all_functions = list(Function.select().where(Function.is_active == True))
        
        # 为管理员分配所有功能权限
        admin_user = User.get(User.username == 'admin')
        
        for function in all_functions:
            if not UserFunction.select().where(
                UserFunction.user == admin_user,
                UserFunction.function == function
            ).exists():
                UserFunction.create(user=admin_user, function=function)
        
        print("管理员权限初始化完成")
        
        # 为普通用户分配部分功能权限（示例）
        # 这里可以添加其他用户的权限分配逻辑
        
    except Exception as e:
        print(f"初始化用户权限失败: {e}")


# 获取用户功能权限
def get_user_functions(user):
    """获取用户的功能权限列表"""
    if user.is_admin:
        # 管理员拥有所有功能权限
        return list(Function.select().where(Function.is_active == True))
    else:
        # 普通用户获取分配的功能权限
        return list(Function.select().join(UserFunction).where(
            UserFunction.user == user,
            Function.is_active == True
        ))


# 检查用户是否有某个功能权限
def has_function_permission(user, function_name):
    """检查用户是否有指定功能的权限"""
    if user.is_admin:
        return True  # 管理员拥有所有权限
    
    try:
        function = Function.get(Function.name == function_name, Function.is_active == True)
        return UserFunction.select().where(
            UserFunction.user == user,
            UserFunction.function == function
        ).exists()
    except Function.DoesNotExist:
        return False


def init_car_models():
    try:
        for name in CAR_MODEL_LIST:
            if not CarModel.select().where(CarModel.name == name).exists():
                CarModel.create(name=name)
        print(f"车型列表初始化完成，共{len(CAR_MODEL_LIST)}个车型")
    except Exception as e:
        print(f"初始化车型列表失败: {e}")


# 初始化用户车型权限
def init_user_car_permissions():
    try:
        all_car_models = list(CarModel.select().where(CarModel.is_active == True))
        admin_user = User.get(User.username == 'admin')
        for car_model in all_car_models:
            if not UserCarModel.select().where(
                UserCarModel.user == admin_user,
                UserCarModel.car_model == car_model
            ).exists():
                UserCarModel.create(user=admin_user, car_model=car_model)
        print("管理员车型权限初始化完成")
    except Exception as e:
        print(f"初始化用户车型权限失败: {e}")


# 获取用户车型权限
def get_user_car_models(user):
    if user.is_admin:
        return list(CarModel.select().where(CarModel.is_active == True))
    else:
        return list(CarModel.select().join(UserCarModel).where(
            UserCarModel.user == user,
            CarModel.is_active == True
        ))


# 检查用户是否有某个车型权限
def has_car_model_permission(user, car_model_name):
    if user.is_admin:
        return True
    try:
        car_model = CarModel.get(CarModel.name == car_model_name, CarModel.is_active == True)
        return UserCarModel.select().where(
            UserCarModel.user == user,
            UserCarModel.car_model == car_model
        ).exists()
    except CarModel.DoesNotExist:
        return False


# 初始化数据库
def init_database():
    create_tables()
    init_default_user()
    init_functions()
    init_user_permissions()
    init_car_models()
    init_user_car_permissions()
